﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net;
using System.Collections.Specialized;
using System.Net.Sockets;
using System.Management;
using Microsoft.Win32;
using System.IO;
using System.Runtime.InteropServices;
using System.Net.NetworkInformation;
using System.Diagnostics;

namespace _180FrameWork.Common
{
    public class MyComputerHelper
    {
        //public static string GetFirstIPAddress()
        //{
        //    var list = GetAllIPAddress();
        //    if (list.Length > 0)
        //        return list[0];
        //    else
        //        return "127.0.0.1";
        //}

        //public static string[] GetAllIPAddress()
        //{
        //    IPAddress[] localIPs = Dns.GetHostAddresses(Dns.GetHostName());
        //    StringCollection ipConllection = new StringCollection();
        //    foreach (IPAddress ip in localIPs)
        //    {
        //        if (ip.AddressFamily == AddressFamily.InterNetwork)
        //            ipConllection.Add(ip.ToString());
        //    }
        //    string[] IpArray = new string[ipConllection.Count];
        //    ipConllection.CopyTo(IpArray, 0);
        //    return IpArray;
        //}

        /// <summary>
        /// 获取计算机描述
        /// </summary>
        /// <returns></returns>
        public static string GetMachineDesc()
        {
            try
            {
                return RegistHelper.mGetValue(Registry.LocalMachine, @"SYSTEM\CurrentControlSet\services\LanmanServer\Parameters", "srvcomment");
            }
            catch { return "未知"; }
        }
        /// <summary>
        /// 设置计算机描述
        /// </summary>
        /// <param name="MachineDesc"></param>
        /// <returns></returns>
        public static int SetMachineDesc(string MachineDesc)
        {
            return RegistHelper.mSetValue(Registry.LocalMachine, @"SYSTEM\CurrentControlSet\services\LanmanServer\Parameters", "srvcomment", MachineDesc, RegistryValueKind.String);
        }

        /// <summary>
        /// 获取计算机名
        /// </summary>
        /// <returns></returns>
        public static string GetMachineName()
        {
            try
            {
                return System.Environment.MachineName;
            }
            catch { return "未知"; }
        }
        /// <summary>
        /// 设置计算机名
        /// </summary>
        /// <param name="MachineName"></param>
        /// <returns></returns>
        public static int SetMachineName(string MachineName)
        {
            return apiSetComputerNameEx(5, MachineName);
        }
        /// <summary>
        /// 获取mac地址和ip地址
        /// </summary>
        /// <returns></returns>
        public static IDictionary<string, string> GetMacAndIP()
        {
            var list = GetMacAndIPByNetWork();
            if (list.Count == 0)
            {
                list = GetMacAndIPByWMI();
            }
            return list;
        }
        /// <summary>
        /// 通过wmi方式获取mac地址和ip地址
        /// </summary>
        /// <returns></returns>
        public static IDictionary<string, string> GetMacAndIPByWMI()
        {
            IDictionary<string, string> list = new Dictionary<string, string>();
            try
            {
                string st = "";
                ManagementClass mc = new ManagementClass("win32_NetworkAdapterConfiguration");
                ManagementObjectCollection moc = mc.GetInstances();
                foreach (ManagementObject mo in moc)
                {
                    if ((bool)mo["IPEnabled"] == true)
                    {
                        //mac = mo["MacAddress"].ToString();
                        System.Array ar = (System.Array)(mo.Properties["IPaddress"].Value);
                        st = ar.GetValue(0).ToString();
                        if (st != "0.0.0.0")
                        {
                            list.Add(mo["MacAddress"].ToString(), st);
                        }
                    }
                }
                //排序
                list = list.OrderBy(m => m.Key).ToDictionary(p=>p.Key, o=>o.Value);
            }
            catch { }
            return list;
        }
        /// <summary>
        /// 通过network方式获取mac地址和ip地址
        /// </summary>
        /// <returns></returns>
        public static IDictionary<string, string> GetMacAndIPByNetWork()
        {
            IDictionary<string, string> list = new Dictionary<string, string>();
            try
            {
                //foreach (var item in NetworkInterface.GetAllNetworkInterfaces())
                //{
                //    if (item.OperationalStatus == OperationalStatus.Up && item.NetworkInterfaceType == NetworkInterfaceType.Ethernet)
                //    {
                //        //先获取需要的接口。两个条件确定当前正在使用的网口。1、接口状态为up；2、接口类型为Ethernet。
                //        foreach (var ipInfo in item.GetIPProperties().UnicastAddresses.ToArray())
                //        {
                //            if (ipInfo.Address.AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork)
                //            {
                //                list.Add(FormatMacAddress(item.GetPhysicalAddress().ToString()), ipInfo.Address.ToString());
                //                break;
                //            }
                //        }
                //    }
                //}
                NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();
                foreach (NetworkInterface adapter in nics)
                {
                    string NetworkInterfaceType = adapter.NetworkInterfaceType.ToString().ToLower();
                    if (NetworkInterfaceType.Equals("ethernet") || NetworkInterfaceType.StartsWith("wireless")) //是以太网卡
                    {
                        string fRegistryKey = "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\" + adapter.Id + "\\Connection";
                        RegistryKey rk = Registry.LocalMachine.OpenSubKey(fRegistryKey, false);
                        if (rk != null)
                        {
                            // 区分 PnpInstanceID     
                            // 如果前面有 PCI 就是本机的真实网卡    
                            // MediaSubType 为 01 则是虚拟网卡，02为无线网卡。    
                            string fPnpInstanceID = rk.GetValue("PnpInstanceID", "").ToString();
                            int fMediaSubType = Convert.ToInt32(rk.GetValue("MediaSubType", 0));
                            if (fPnpInstanceID.Length > 3 && fPnpInstanceID.Substring(0, 3) == "PCI") //是物理网卡
                            {
                                string macAddress = adapter.GetPhysicalAddress().ToString();
                                string ipAddress = "未知";
                                foreach (var ipInfo in adapter.GetIPProperties().UnicastAddresses.ToArray())
                                {
                                    if (ipInfo.Address.AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork)
                                    {
                                        ipAddress = ipInfo.Address.ToString();
                                        break;
                                    }
                                }
                                list.Add(FormatMacAddress(macAddress), ipAddress);
                                       
                                //macAddress = adapter.GetPhysicalAddress().ToString();
                                //list.Add(FormatMacAddress(adapter.GetPhysicalAddress().ToString()), ipInfo.Address.ToString());
                            }
                            else if (fMediaSubType == 1) //虚拟网卡
                                continue;
                            else if (fMediaSubType == 2) //无线网卡(上面判断Ethernet时已经排除了)
                            {
                                string macAddress = adapter.GetPhysicalAddress().ToString();
                                string ipAddress = "未知";
                                foreach (var ipInfo in adapter.GetIPProperties().UnicastAddresses.ToArray())
                                {
                                    if (ipInfo.Address.AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork)
                                    {
                                        ipAddress = ipInfo.Address.ToString();
                                        break;
                                    }
                                }
                                list.Add(FormatMacAddress(macAddress), ipAddress);
                            }
                        }
                    }
                }
                //排序
                list = list.OrderBy(m => m.Key).ToDictionary(p => p.Key, o => o.Value);
            }
            catch { }
            return list;
        }

        //public string getMacAddress()
        //{
        //    string macAddress = null;
        //    try
        //    {
        //        NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();
        //        foreach (NetworkInterface adapter in nics)
        //        {
        //            string NetworkInterfaceType = adapter.NetworkInterfaceType.ToString().ToLower();
        //            if (NetworkInterfaceType.Equals("ethernet") || NetworkInterfaceType.StartsWith("wireless")) //是以太网卡
        //            {
        //                string fRegistryKey = "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\" + adapter.Id + "\\Connection";
        //                RegistryKey rk = Registry.LocalMachine.OpenSubKey(fRegistryKey, false);
        //                if (rk != null)
        //                {
        //                    // 区分 PnpInstanceID     
        //                    // 如果前面有 PCI 就是本机的真实网卡    
        //                    // MediaSubType 为 01 则是虚拟网卡，02为无线网卡。    
        //                    string fPnpInstanceID = rk.GetValue("PnpInstanceID", "").ToString();
        //                    int fMediaSubType = Convert.ToInt32(rk.GetValue("MediaSubType", 0));
        //                    if (fPnpInstanceID.Length > 3 && fPnpInstanceID.Substring(0, 3) == "PCI") //是物理网卡
        //                    {
        //                        macAddress = adapter.GetPhysicalAddress().ToString();
        //                        break;
        //                    }
        //                    else if (fMediaSubType == 1) //虚拟网卡
        //                        continue;
        //                    else if (fMediaSubType == 2) //无线网卡(上面判断Ethernet时已经排除了)
        //                        continue;
        //                }
        //            }
        //        }
        //    }
        //    catch
        //    {
        //        macAddress = null;
        //    }
        //    return macAddress;
        //}

        /// <summary>
        /// ip地址格式化
        /// </summary>
        /// <param name="mac"></param>
        /// <returns></returns>
        private static string FormatMacAddress(string mac)
        {
            if (mac.Length == 12)
            {
                StringBuilder str = new StringBuilder();
                str.Append(mac[0]);
                str.Append(mac[1]);
                str.Append(":");
                str.Append(mac[2]);
                str.Append(mac[3]);
                str.Append(":");
                str.Append(mac[4]);
                str.Append(mac[5]);
                str.Append(":");
                str.Append(mac[6]);
                str.Append(mac[7]);
                str.Append(":");
                str.Append(mac[8]);
                str.Append(mac[9]);
                str.Append(":");
                str.Append(mac[10]);
                str.Append(mac[11]);
                return str.ToString();
            }
            else
            {
                return mac;
            }
        }


        //public static string GetWorkgroup() { return GetWorkgroupByWMI(); }

        //public static string GetWorkgroupByWMI()
        //{
        //    try
        //    {
        //        string st = "";
        //        ManagementObject computer_system = new ManagementObject(string.Format("Win32-ComputerSystem.Name='{0}'", Environment.MachineName));
        //        st = computer_system["Workgroup"].ToString();
        //        // ManagementClass mc = new ManagementClass("win32_ComputerSystem");
        //        //ManagementObjectCollection moc = mc.GetInstances();
        //        //foreach (ManagementObject mo in moc)
        //        //{
        //        //    if (mo["Workgroup"] != null)
        //        //    {
        //        //        st = mo["Workgroup"].ToString();
        //        //        break;
        //        //    }
        //        //}

        //        return st;
        //    }
        //    catch { return "未知"; }
        //}
        /// <summary>
        /// 获取内存大小
        /// </summary>
        /// <returns></returns>
        public static string GetMemoryBank() {
            return GetMemoryBankByWMI();
        }
        /// <summary>
        /// 通过wmi方式获取内存大小
        /// </summary>
        /// <returns></returns>
        public static string GetMemoryBankByWMI()
        {
            try
            {
                string st = "";
               //st= new Microsoft.VisualBasic.Devices.ComputerInfo().TotalPhysicalMemory.ToString();

                ManagementClass mc = new ManagementClass("win32_ComputerSystem");
                ManagementObjectCollection moc = mc.GetInstances();
                foreach (ManagementObject mo in moc)
                {
                    st = mo["TotalPhysicalMemory"].ToString();
                    break;
                }
                decimal mb = decimal.Parse(st) / 1024 / 1024 / 1024;
                return mb.ToString("N2").Replace(",", "") + "G";
            }
            catch { return "未知"; }
        }
        /// <summary>
        /// 获取磁盘空间大小
        /// </summary>
        /// <returns></returns>
        public static string GetDisk()
        {
            return GetDiskByWMI();
        }
        /// <summary>
        /// 获取磁盘序列号
        /// </summary>
        /// <returns></returns>
        public static IList<string> GetDiskSerialNumber()
        {
            return GetDiskSerialNumberByWMI();
        }
        /// <summary>
        /// 通过wmi方式获取磁盘空间大小
        /// </summary>
        /// <returns></returns>
        public static string GetDiskByWMI()
        {
            try
            {
                decimal disk = 0;
                ManagementClass mc = new ManagementClass("win32_DiskPartition");
                //ManagementClass mc = new ManagementClass("win32_LogicalDisk");
                ManagementObjectCollection moc = mc.GetInstances();

                foreach (ManagementObject mo in moc)
                {
                    try
                    {
                        decimal currentDisk = 0;
                        if (decimal.TryParse(mo["Size"].ToString(), out currentDisk))
                            disk += (currentDisk / 1024 / 1024 / 1024);
                    }
                    catch
                    {
                    }
                }
                return disk.ToString("N2").Replace(",", "") + "G";
            }
            catch { return "未知"; }
        }
        /// <summary>
        /// 通过wmi方式获取磁盘序列号
        /// </summary>
        /// <returns></returns>
        public static IList<string> GetDiskSerialNumberByWMI()
        {
            IList<string> list = new List<string>();
            try
            {
                ManagementClass mc = new ManagementClass("Win32_DiskDrive");
                ManagementObjectCollection moc = mc.GetInstances();
                foreach (var mo in moc)
                {
                    list.Add(mo["Model"].ToString().Trim());//记录获得的磁盘序列号        
                }
                ////创建ManagementObjectSearcher对象
                //ManagementObjectSearcher searcher = new ManagementObjectSearcher("SELECT * FROM Win32_PhysicalMedia");

                ////调用ManagementObjectSearcher类的Get方法取得硬盘序列号
                //foreach (ManagementObject mo in searcher.Get())
                //{
                //    list.Add( mo["SerialNumber"].ToString().Trim());//记录获得的磁盘序列号                    
                //}
            }
            catch { }
            return list;
        }
        /// <summary>
        /// 获取系统版本
        /// </summary>
        /// <returns></returns>
        public static string GetOSVersion()
        {
            return GetOSVersionByWMI();
        }

        public static string GetOSVersionByWMI()
        {
            try
            {
                string result = string.Empty;
                ManagementObjectSearcher searcher = new ManagementObjectSearcher("SELECT Caption FROM Win32_OperatingSystem");
                foreach (ManagementObject os in searcher.Get())
                {
                    result = os["Caption"].ToString();
                    break;
                }
                return result;
            }
            catch
            {
                return "未知";
            }
        }
        public static string GetOSVersionByEnvironment()
        {
            try
            {
                return System.Environment.OSVersion.ToString();
                //string ver = "未知";
                //switch (System.Environment.OSVersion.Version.Major + "." + System.Environment.OSVersion.Version.Minor)
                //{
                //    case "5.0":
                //        ver = "win2000";
                //        break;
                //    case "5.1":
                //        ver = "winxp";
                //        break;
                //    case "5.2":
                //        ver = "win2003";
                //        break;
                //    case "6.0":
                //        ver = "win2008";
                //        break;
                //    case "6.1":
                //        ver = "win7";
                //        break;
                //    case "6.2":
                //        ver = "win8";
                //        break;
                //    case "10.0":
                //        ver = "win10";
                //        break;
                //}
                //return ver;
            }
            catch { return "未知"; }
        }
        /// <summary>
        /// 获取cpu信息
        /// </summary>
        /// <returns></returns>
        public static string GetCpu() {
            return GetCupFromRegister();
        }
        /// <summary>
        /// 通过wmi方式获取CPU信息
        /// </summary>
        /// <returns></returns>
        public static string GetCpuByWMI()
        {
            try
            {
                string st = "";
                ManagementClass mc = new ManagementClass("win32_Processor");
                ManagementObjectCollection moc = mc.GetInstances();
                foreach (ManagementObject mo in moc)
                {
                    //foreach (var p in mo.Properties)
                    //{
                    //    st += p.Name+"="+ p.Value + ";";
                    //}
                    //AddressWidth=32;Architecture=0;Availability=3;Caption=x86 Family 6 Model 42 Stepping 7;ConfigManagerErrorCode=;ConfigManagerUserConfig=;CpuStatus=1;CreationClassName=Win32_Processor;CurrentClockSpeed=3292;CurrentVoltage=0;DataWidth=32;Description=x86 Family 6 Model 42 Stepping 7;DeviceID=CPU0;ErrorCleared=;ErrorDescription=;ExtClock=100;Family=176;InstallDate=;L2CacheSize=256;L2CacheSpeed=3292;LastErrorCode=;Level=6;LoadPercentage=4;Manufacturer=GenuineIntel;MaxClockSpeed=3292;Name=Intel Pentium III Xeon 处理器;NumberOfCores=2;NumberOfLogicalProcessors=4;OtherFamilyDescription=;PNPDeviceID=;PowerManagementCapabilities=;PowerManagementSupported=False;ProcessorId=BFEBFBFF000206A7;ProcessorType=3;Revision=10759;Role=CPU;SocketDesignation=CPU 1;Status=OK;StatusInfo=3;Stepping=7;SystemCreationClassName=Win32_ComputerSystem;SystemName=pc0011;UniqueId=;UpgradeMethod=9;Version=型号 10，步进 7;VoltageCaps=;
                    st = mo["Name"].ToString().Trim();
                    break;

                }
                return st;
            }
            catch { return "未知"; }
        }

        public static string GetCupFromRegister()
        {
            var str = RegistHelper.mGetValue(Registry.LocalMachine, @"HARDWARE\DESCRIPTION\System\CentralProcessor\0", "ProcessorNameString");

            return MyStringHelper.TrimStart(MyStringHelper.TrimRight(str));
        }

        /// <summary>  
        /// 是否能 Ping 通指定的主机  
        /// </summary>  
        /// <param name="ip">ip 地址或主机名或域名</param>  
        /// <returns>true 通，false 不通</returns>  
        public static bool PingTest(string ip)
        {
            try
            {
                System.Net.NetworkInformation.Ping p = new System.Net.NetworkInformation.Ping();
                System.Net.NetworkInformation.PingOptions options = new System.Net.NetworkInformation.PingOptions();
                options.DontFragment = true;
                string data = "Test Data!";
                byte[] buffer = Encoding.ASCII.GetBytes(data);
                int timeout = 5000; // Timeout 时间，单位：毫秒  
                System.Net.NetworkInformation.PingReply reply = p.Send(ip, timeout, buffer, options);
                if (reply == null || reply.Status == System.Net.NetworkInformation.IPStatus.Success)
                    return true;

                return false;
            }
            catch (System.Net.NetworkInformation.PingException e)
            {
                return false;
            }
        }
        /// <summary>
        /// 设置屏保
        /// </summary>
        /// <param name="ImageDirectory"></param>
        /// <param name="ScreenSaveTimeOut"></param>
        /// <param name="scrnsaveUrl"></param>
        /// <returns></returns>
        public static int SetScreenSaver(string ImageDirectory, string ScreenSaveTimeOut, string scrnsaveUrl)
        {
            int result = 0;
            try
            {
                RegistHelper.mCreateSubKey(Registry.CurrentUser, @"Control Panel\Screen Saver.Slideshow");
                RegistHelper.mSetValue(Registry.CurrentUser, @"Control Panel\Screen Saver.Slideshow", "ImageDirectory", ImageDirectory, RegistryValueKind.String);
                RegistHelper.mSetValue(Registry.CurrentUser, @"Control Panel\Screen Saver.Slideshow", "AllowStretching", "1", RegistryValueKind.DWord);
                RegistHelper.mCreateSubKey(Registry.CurrentUser, @"Control Panel\Desktop");
                RegistHelper.mSetValue(Registry.CurrentUser, @"Control Panel\Desktop", "SCRNSAVE.EXE", scrnsaveUrl, RegistryValueKind.String);
                RegistHelper.mSetValue(Registry.CurrentUser, @"Control Panel\Desktop", "ScreenSaveTimeOut", ScreenSaveTimeOut, RegistryValueKind.String);
                RegistHelper.mSetValue(Registry.CurrentUser, @"Control Panel\Desktop", "ScreenSaveActive", "1", RegistryValueKind.String);
                result = 1;
            }
            catch (Exception)
            {
                throw;
            }
            return result;
        }
        /// <summary>
        /// 设置背景
        /// </summary>
        /// <param name="path"></param>
        /// <param name="fileName"></param>
        /// <returns></returns>
        public static int SetBackgroud(string path, string fileName)
        {
            int result = 0;
            if (File.Exists(fileName))
            {
                string tempFile = path + "\\" + Path.GetFileName(fileName);
                StringBuilder strSavePath = new StringBuilder(tempFile);
                result = SystemParametersInfo(20, 1, strSavePath, 0x2);
                RegistHelper.mSetValue(Registry.CurrentUser, @"Control Panel\Desktop", "Wallpaper", tempFile, RegistryValueKind.String);
                RegistHelper.mSetValue(Registry.CurrentUser, @"Control Panel\Desktop", "WallpaperStyle", "2", RegistryValueKind.String);
                result = 1;
            }
            return result;
        }

        /// <summary>
        /// 获取工作组 create by dkw
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        public static string GetWorkGroup()
        {
            //string str       = @"wmic computersystem get domain";// string.Format("wmic computersystem where name=\"{0}\" call JoinDomainOrWorkgroup Name=\"{1}\"", "PC0927", "ABDS");
            //string result    = RunCmd(str);
            //string [] values = result.Split(new String[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries);
            //return MyStringHelper.TrimAll(values[4]);
            try
            {
                string st = "";
                ManagementObjectSearcher mos = new ManagementObjectSearcher(@"root\CIMV2", @"SELECT * FROM Win32_ComputerSystem");
                foreach (ManagementObject mo in mos.Get())
                {
                    st = (mo["Domain"].ToString());
                    break;
                }
                return st;
            }
            catch
            {
                return "未知";
            }
        }

        /// <summary>
        /// 设置工作组 create by dkw
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        public static int SetWorkGroup(string GroupName)
        {
            try
            {
                //string str = string.Format("wmic computersystem where name=\"{0}\" call JoinDomainOrWorkgroup Name=\"{1}\"", PcName, GroupName);
                //RunCmd(str);
                ManagementObject manage = new ManagementObject(string.Format("Win32_ComputerSystem.Name='{0}'", Environment.MachineName));
                object[] args = { GroupName, null, null, null };
                manage.InvokeMethod("JoinDomainOrWorkgroup", args);
                return 1;
            }
            catch
            {
                return 0;
            }
        }

        ///// <summary>
        ///// 执行cmd命令 create by dkw
        ///// </summary>
        ///// <param name="command"></param>
        ///// <returns></returns>
        //public static string RunCmd(string command)
        //{
        //    StringBuilder cmdBuilder = new StringBuilder();
        //    cmdBuilder.AppendLine(command);
        //    Process pro = new Process();
        //    var si = new ProcessStartInfo();
        //    si.FileName = "cmd.exe";
        //    si.CreateNoWindow = true;
        //    si.RedirectStandardInput = true;
        //    si.RedirectStandardOutput = true;
        //    si.RedirectStandardError = true;
        //    si.UseShellExecute = false;
        //    pro.StartInfo = si;
        //    pro.Start();
        //    pro.StandardInput.Write(cmdBuilder.ToString());
        //    pro.StandardInput.Flush();
        //    pro.StandardInput.Close();
        //    pro.WaitForExit();
        //    var str = pro.StandardOutput.ReadToEnd();
        //    pro.Close();
        //    return str;
        //}

        /// <summary>
        /// 查询或设置系统级参数
        /// </summary>
        /// <param name="uAction"></param>
        /// <param name="uParam"></param>
        /// <param name="lpvParam"></param>
        /// <param name="fuWinIni"></param>
        /// <example></example>
        /// <returns></returns>
        [DllImport("user32.dll", EntryPoint = "SystemParametersInfo")]
        private static extern int SystemParametersInfo(int uAction, int uParam, StringBuilder lpvParam, int fuWinIni);
        /// <summary>
        /// 
        /// </summary>
        /// <param name="type"></param>
        /// <param name="ipComputerName"></param>
        /// <returns></returns>
        [DllImport("kernel32.dll", EntryPoint = "SetComputerNameEx")]
        private static extern int apiSetComputerNameEx(int type, string ipComputerName);
    }
}
